home *** CD-ROM | disk | FTP | other *** search
/ Windows Game Programming for Dummies (2nd Edition) / WinGamProgFD.iso / pc / DirectX SDK / DXSDK / samples / Multimedia / VBSamples / Direct3D / Billboard / billboard.frm (.txt) next >
Encoding:
Visual Basic Form  |  2001-10-08  |  22.8 KB  |  576 lines

  1. VERSION 5.00
  2. Begin VB.Form Form1 
  3.    Caption         =   "Form1"
  4.    ClientHeight    =   4290
  5.    ClientLeft      =   60
  6.    ClientTop       =   345
  7.    ClientWidth     =   5580
  8.    Icon            =   "billboard.frx":0000
  9.    LinkTopic       =   "Form1"
  10.    ScaleHeight     =   286
  11.    ScaleMode       =   3  'Pixel
  12.    ScaleWidth      =   372
  13.    StartUpPosition =   3  'Windows Default
  14. Attribute VB_Name = "Form1"
  15. Attribute VB_GlobalNameSpace = False
  16. Attribute VB_Creatable = False
  17. Attribute VB_PredeclaredId = True
  18. Attribute VB_Exposed = False
  19. '-----------------------------------------------------------------------------
  20. ' File: Billboard.frm
  21. ' Desc: Example code showing how to do billboarding. The sample uses
  22. '       billboarding to draw some trees.
  23. '       Note: this implementation is for billboards that are fixed to rotate
  24. '       about the Y-axis, which is good for things like trees. For
  25. '       unconstrained billboards, like explosions in a flight sim, the
  26. '       technique is the same, but the the billboards are positioned slightly
  27. '       different. Try using the inverse of the view matrix, TL-vertices, or
  28. '       some other technique.
  29. ' Copyright (C) 1999-2001 Microsoft Corporation. All rights reserved.
  30. '-----------------------------------------------------------------------------
  31. Option Explicit
  32. '-----------------------------------------------------------------------------
  33. ' Defines, constants, and global variables
  34. '-----------------------------------------------------------------------------
  35. Const NUM_TREES = 200
  36. Const D3DFVF_TREEVERTEX = (D3DFVF_XYZ Or D3DFVF_DIFFUSE Or D3DFVF_TEX1)
  37. Const NUMTREETEXTURES = 3
  38. ' Custom vertex type for the trees
  39. Private Type TREEVERTEX
  40.     p As D3DVECTOR
  41.     color As Long
  42.     tu As Single
  43.     tv As Single
  44. End Type
  45. Dim m_bInit As Boolean                  ' Indicates that d3d has been initialized
  46. Dim m_bMinimized As Boolean             ' Indicates that display window is minimized
  47. '-----------------------------------------------------------------------------
  48. ' Name: Tree
  49. ' Desc: Simple structure to hold data for rendering a tree
  50. '-----------------------------------------------------------------------------
  51. Private Type TREE
  52.     v(3) As TREEVERTEX
  53.     vPos As D3DVECTOR
  54.     iTreeTexture As Long
  55.     iNext As Long
  56.     dist As Single
  57. End Type
  58. Private Type HILLVERTEX
  59.     x As Single
  60.     y As Single
  61.     z As Single
  62.     tu As Single
  63.     tv As Single
  64. End Type
  65. Dim m_vEyePt As D3DVECTOR
  66. Dim m_strTreeTextures(3) As String
  67. Dim m_media As String
  68. Dim m_Terrain As CD3DMesh
  69. Dim m_SkyBox  As CD3DMesh              ' Skybox background object
  70. Dim m_TreeVB As Direct3DVertexBuffer8  ' Vertex buffer for rendering a tree
  71. Dim m_TreeTextures(NUMTREETEXTURES)    ' Tree images
  72. Dim m_matBillboardMatrix As D3DMATRIX   ' Used for billboard orientation
  73. Dim m_Trees(NUM_TREES)  As TREE                ' Array of tree info
  74. Dim m_fTime As Single
  75. Dim m_iTreeHead As Long
  76. Dim m_iSortHead As Long
  77. '-----------------------------------------------------------------------------
  78. ' Name: Form_Load()
  79. ' Desc:
  80. '-----------------------------------------------------------------------------
  81. Private Sub Form_Load()
  82.     Me.Show
  83.     DoEvents
  84.     'Setup defaults
  85.     Init
  86.      ' Initialize D3D
  87.     ' Note: D3DUtil_Init will attempt to use D3D Hardware acceleartion.
  88.     ' If it is not available it attempt to use the Software Reference Rasterizer.
  89.     ' If all fail it will display a message box indicating so.
  90.     '
  91.     m_bInit = D3DUtil_Init(Me.hwnd, True, 0, 0, D3DDEVTYPE_HAL, Nothing)
  92.     If Not (m_bInit) Then End
  93.     ' Find media and set media directory
  94.     m_media = FindMediaDir("Tree02S.tga")
  95.     D3DUtil_SetMediaPath m_media
  96.     ' Initialize Application Data
  97.     OneTimeSceneInit
  98.     ' Create and load mesh objects
  99.     InitDeviceObjects
  100.     ' Sets the state for those objects and the current D3D device
  101.     ' (setup camera and lights etc)
  102.     RestoreDeviceObjects
  103.     ' Start application timer
  104.     DXUtil_Timer TIMER_start
  105.     ' Run the simulation forever
  106.     ' See Form_Keydown for exit processing
  107.     Do While True
  108.         ' Increment the simulation
  109.         FrameMove
  110.         
  111.         ' Render one image of the simulation
  112.         If Render Then 'Success
  113.             
  114.             ' Present the image to the screen
  115.             D3DUtil_PresentAll g_focushwnd
  116.         End If
  117.         
  118.         ' Allow for events to get processed
  119.         DoEvents
  120.         
  121.     Loop
  122. End Sub
  123. '-----------------------------------------------------------------------------
  124. ' Name: Form_KeyDown()
  125. ' Desc: Process key messages for exit and change device
  126. '-----------------------------------------------------------------------------
  127. Private Sub Form_KeyDown(KeyCode As Integer, Shift As Integer)
  128.      
  129.      Dim hr As Long
  130.      
  131.      Select Case KeyCode
  132.         
  133.         Case vbKeyEscape
  134.             Unload Me
  135.             
  136.         Case vbKeyF2
  137.                 
  138.             ' Pause the timer
  139.             DXUtil_Timer TIMER_STOP
  140.             
  141.             ' Bring up the device selection dialog
  142.             ' we pass in the form so the selection process
  143.             ' can make calls into InitDeviceObjects
  144.             ' and RestoreDeviceObjects
  145.             frmSelectDevice.SelectDevice Me
  146.             
  147.             ' Restart the timer
  148.             DXUtil_Timer TIMER_start
  149.             
  150.         Case vbKeyReturn
  151.         
  152.             ' Check for Alt-Enter if not pressed exit
  153.             If Shift <> 4 Then Exit Sub
  154.             
  155.             ' If we are windowed go fullscreen
  156.             ' If we are fullscreen returned to windowed
  157.             If g_d3dpp.Windowed Then
  158.                  hr = D3DUtil_ResetFullscreen
  159.             Else
  160.                  hr = D3DUtil_ResetWindowed
  161.             End If
  162.                              
  163.             ' Call Restore after ever mode change
  164.             ' because calling reset looses state that needs to
  165.             ' be reinitialized
  166.             If (hr = D3D_OK) Then
  167.                 RestoreDeviceObjects
  168.             End If
  169.            
  170.     End Select
  171. End Sub
  172. '-----------------------------------------------------------------------------
  173. ' Name: Form_Resize()
  174. ' Desc: hadle resizing of the D3D backbuffer
  175. '-----------------------------------------------------------------------------
  176. Private Sub Form_Resize()
  177.     ' If D3D is not initialized then exit
  178.     If Not m_bInit Then Exit Sub
  179.     ' If we are in a minimized state stop the timer and exit
  180.     If Me.WindowState = vbMinimized Then
  181.         DXUtil_Timer TIMER_STOP
  182.         m_bMinimized = True
  183.         Exit Sub
  184.         
  185.     ' If we just went from a minimized state to maximized
  186.     ' restart the timer
  187.     Else
  188.         If m_bMinimized = True Then
  189.             DXUtil_Timer TIMER_start
  190.             m_bMinimized = False
  191.         End If
  192.     End If
  193.     ' Dont let the window get too small
  194.     If Me.ScaleWidth < 10 Then
  195.         Me.width = Screen.TwipsPerPixelX * 10
  196.         Exit Sub
  197.     End If
  198.     If Me.ScaleHeight < 10 Then
  199.         Me.height = Screen.TwipsPerPixelY * 10
  200.         Exit Sub
  201.     End If
  202.         
  203.     'reset and resize our D3D backbuffer to the size of the window
  204.     D3DUtil_ResizeWindowed Me.hwnd
  205.     'All state get losts after a reset so we need to reinitialze it here
  206.     RestoreDeviceObjects
  207. End Sub
  208. '-----------------------------------------------------------------------------
  209. ' Name: Form_Unload()
  210. ' Desc:
  211. '-----------------------------------------------------------------------------
  212. Private Sub Form_Unload(Cancel As Integer)
  213.     DeleteDeviceObjects
  214.     End
  215. End Sub
  216. ' Simple function to define "hilliness" for terrain
  217. Function HeightField(x As Single, y As Single) As Single
  218.     HeightField = 9 * (Cos(x / 20 + 0.2) * Cos(y / 15 - 0.2) + 1#)
  219. End Function
  220. Sub Init()
  221.     m_strTreeTextures(0) = "Tree02S.tga"
  222.     m_strTreeTextures(1) = "Tree35S.tga"
  223.     m_strTreeTextures(2) = "Tree01S.tga"
  224.     Me.Caption = ("Billboard: D3D Billboarding Example")
  225.     Set m_SkyBox = New CD3DMesh
  226.     Set m_Terrain = New CD3DMesh
  227.     Set m_TreeVB = Nothing
  228. End Sub
  229. '-----------------------------------------------------------------------------
  230. ' Name: OneTimeSceneInit()
  231. ' Desc: Called during initial app startup, this function performs all the
  232. '       permanent initialization.
  233. '-----------------------------------------------------------------------------
  234. Sub OneTimeSceneInit()
  235.     Dim i As Long
  236.     Dim fTheta As Single, fRadius As Single, fWidth As Single, fHeight As Single
  237.     Dim r As Long, g As Long, b As Long, treecolor As Long
  238.     Rnd (1)
  239.     ' Initialize the tree data
  240.     For i = 0 To NUM_TREES - 1
  241.         ' Position the trees randomly
  242.         fTheta = 2 * g_pi * Rnd()
  243.         fRadius = 25 + 55 * Rnd()
  244.         m_Trees(i).vPos.x = fRadius * Sin(fTheta)
  245.         m_Trees(i).vPos.z = fRadius * Cos(fTheta)
  246.         m_Trees(i).vPos.y = HeightField(m_Trees(i).vPos.x, m_Trees(i).vPos.z)
  247.         ' Size the trees randomly
  248.         fWidth = 1 + 0.2 * (Rnd() - Rnd())
  249.         fHeight = 1.4 + 0.4 * (Rnd() - Rnd())
  250.         ' Each tree is a random color between red and green
  251.          r = (255 - 190) + CLng(190 * Rnd())
  252.          g = (255 - 190) + CLng(190 * Rnd())
  253.          b = 0
  254.          treecolor = &HFF000000 + r * 2 ^ 16 + g * 2 ^ 8 + b
  255.         m_Trees(i).v(0).p = vec3(-fWidth, 0 * fHeight, 0)
  256.         m_Trees(i).v(0).color = treecolor
  257.         m_Trees(i).v(0).tu = 0: m_Trees(i).v(0).tv = 1
  258.         m_Trees(i).v(1).p = vec3(-fWidth, 2 * fHeight, 0)
  259.         m_Trees(i).v(1).color = treecolor
  260.         m_Trees(i).v(1).tu = 0: m_Trees(i).v(1).tv = 0
  261.         m_Trees(i).v(2).p = vec3(fWidth, 0 * fHeight, 0)
  262.         m_Trees(i).v(2).color = treecolor
  263.         m_Trees(i).v(2).tu = 1:      m_Trees(i).v(2).tv = 1
  264.         m_Trees(i).v(3).p = vec3(fWidth, 2 * fHeight, 0)
  265.         m_Trees(i).v(3).color = treecolor
  266.         m_Trees(i).v(3).tu = 1:      m_Trees(i).v(3).tv = 0
  267.         ' Size the trees randomly
  268.         m_Trees(i).iTreeTexture = CLng((NUMTREETEXTURES - 1) * Rnd())
  269.         m_Trees(i).iNext = i + 1
  270.     Next
  271.     m_Trees(NUM_TREES - 1).iNext = -1  'use -1 to indicate end of the list
  272. End Sub
  273. '-----------------------------------------------------------------------------
  274. ' Name: Sort
  275. ' Desc: Callback function for sorting trees in back-to-front order
  276. '-----------------------------------------------------------------------------
  277. Sub DoSort()
  278.     Dim i As Long
  279.     Dim dx As Single, dz As Single, dist As Single
  280.     'calculate the square of the distance to the eyept
  281.     'to best approximate sort order
  282.     'CONSIDER transforming the position into screen space and sorting on z/w
  283.     For i = 0 To NUM_TREES - 1
  284.         dx = m_Trees(i).vPos.x - m_vEyePt.x
  285.         dz = m_Trees(i).vPos.z - m_vEyePt.z
  286.         m_Trees(i).dist = dx * dx + dz * dz
  287.     Next
  288.     Dim iAtU As Long
  289.     Dim iPrevU As Long
  290.     Dim iNextU As Long
  291.     iAtU = m_iTreeHead
  292.     iPrevU = -1
  293.     iNextU = -1
  294.     m_iSortHead = -1
  295.     Dim z As Long
  296.     Dim q As Long
  297.         
  298.     Do While iAtU <> -1
  299.         dist = m_Trees(iAtU).dist
  300.         
  301.         iNextU = m_Trees(iAtU).iNext
  302.         InsertIntoList iAtU, dist
  303.                 
  304.         
  305.         
  306.         'advance to next item in Unsorted list
  307.         iPrevU = iAtU
  308.         iAtU = iNextU
  309.         
  310.     Loop
  311.      
  312.     m_iTreeHead = m_iSortHead
  313. End Sub
  314. Sub InsertIntoList(iNode As Long, dist2 As Single)
  315.     Dim iAtS As Long
  316.     Dim iPrevS As Long
  317.             
  318.     iAtS = m_iSortHead
  319.     iPrevS = -1
  320.     'If Sorted list is empty add first node
  321.     If iAtS = -1 Then
  322.         m_iSortHead = iNode
  323.         m_Trees(iNode).iNext = -1
  324.         Exit Sub
  325.     End If
  326.     'see if we need to add at begining
  327.     If m_Trees(m_iSortHead).dist < dist2 Then
  328.         m_Trees(iNode).iNext = m_iSortHead
  329.         m_iSortHead = iNode
  330.         Exit Sub
  331.     End If
  332.     'we dont have an empty list
  333.     'we dont need to add to front of list
  334.     Do While iAtS <> -1
  335.         
  336.         If m_Trees(iAtS).dist < dist2 Then
  337.         
  338.             'add to sorted list
  339.             m_Trees(iNode).iNext = m_Trees(iPrevS).iNext
  340.             m_Trees(iPrevS).iNext = iNode
  341.             Exit Sub
  342.         End If
  343.                 
  344.         'advance to next item in  sorted list
  345.         iPrevS = iAtS
  346.         iAtS = m_Trees(iAtS).iNext
  347.         
  348.     Loop
  349.     'must go at end of list
  350.     m_Trees(iPrevS).iNext = iNode
  351.     m_Trees(iNode).iNext = -1
  352. End Sub
  353. '-----------------------------------------------------------------------------
  354. ' Name: FrameMove()
  355. ' Desc: Called once per frame, the call is the entry point for animating
  356. '       the scene.
  357. '-----------------------------------------------------------------------------
  358. Sub FrameMove()
  359.     m_fTime = DXUtil_Timer(TIMER_GETAPPTIME)
  360.     ' Get the eye and lookat points from the camera's path
  361.     Dim vUpVec As D3DVECTOR, vEyePt As D3DVECTOR, vLookAtpt As D3DVECTOR
  362.     vUpVec = vec3(0, 1, 0)
  363.     vEyePt.x = 30 * Cos(0.8 * (m_fTime + 1))
  364.     vEyePt.z = 30 * Sin(0.8 * (m_fTime + 1))
  365.     vEyePt.y = 4 + HeightField(vEyePt.x, vEyePt.z)
  366.     vLookAtpt.x = 30 * Cos(0.8 * (m_fTime + 1.5))
  367.     vLookAtpt.z = 30 * Sin(0.8 * (m_fTime + 1.5))
  368.     vLookAtpt.y = vEyePt.y - 1
  369.     ' Set the app view matrix for normal viewing
  370.     Dim matView As D3DMATRIX
  371.     D3DXMatrixLookAtLH matView, vEyePt, vLookAtpt, vUpVec
  372.     g_dev.SetTransform D3DTS_VIEW, matView
  373.     ' Set up a rotation matrix to orient the billboard towards the camera.
  374.     Dim vDir As D3DVECTOR
  375.     D3DXVec3Subtract vDir, vLookAtpt, vEyePt
  376.     If (vDir.x > 0) Then
  377.         D3DXMatrixRotationY m_matBillboardMatrix, -Atn(vDir.z / vDir.x) + (g_pi / 2)
  378.     Else
  379.         D3DXMatrixRotationY m_matBillboardMatrix, -Atn(vDir.z / vDir.x) - (g_pi / 2)
  380.     End If
  381.     ' Sort trees in back-to-front order
  382.     m_vEyePt = vEyePt
  383.     DoSort
  384. End Sub
  385. '-----------------------------------------------------------------------------
  386. ' Name: DrawTrees()
  387. ' Desc:
  388. '-----------------------------------------------------------------------------
  389. Sub DrawTrees()
  390.     Dim i As Long
  391.     ' Set diffuse blending for alpha set in vertices.
  392.     g_dev.SetRenderState D3DRS_ALPHABLENDENABLE, 1  'TRUE
  393.     g_dev.SetRenderState D3DRS_SRCBLEND, D3DBLEND_SRCALPHA
  394.     g_dev.SetRenderState D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA
  395.     ' Enable alpha testing (skips pixels with less than a certain alpha.)
  396.     If ((g_d3dCaps.AlphaCmpCaps And D3DPCMPCAPS_GREATEREQUAL) = D3DPCMPCAPS_GREATEREQUAL) Then
  397.         g_dev.SetRenderState D3DRS_ALPHATESTENABLE, 1 'TRUE
  398.         g_dev.SetRenderState D3DRS_ALPHAREF, &H8&
  399.         g_dev.SetRenderState D3DRS_ALPHAFUNC, D3DCMP_GREATEREQUAL
  400.     End If
  401.     ' Loop through and render all trees
  402.     'For i = 0 To NUM_TREES
  403.     i = m_iTreeHead
  404.     Do While i <> -1
  405.         
  406.         ' Set the tree texture
  407.         g_dev.SetTexture 0, m_TreeTextures(m_Trees(i).iTreeTexture)
  408.         ' Translate the billboard into place
  409.         m_matBillboardMatrix.m41 = m_Trees(i).vPos.x
  410.         m_matBillboardMatrix.m42 = m_Trees(i).vPos.y
  411.         m_matBillboardMatrix.m43 = m_Trees(i).vPos.z
  412.         g_dev.SetTransform D3DTS_WORLD, m_matBillboardMatrix
  413.         ' Copy tree mesh into vertexbuffer
  414.         Dim v As TREEVERTEX
  415.         D3DVertexBuffer8SetData m_TreeVB, 0, Len(v) * 4, 0, m_Trees(i).v(0)
  416.         
  417.         ' Render the billboards one at a time
  418.         ' CONSIDER: putting this in larger vertex buffers sorted by texture
  419.         g_dev.SetStreamSource 0, m_TreeVB, Len(v)
  420.         g_dev.SetVertexShader D3DFVF_TREEVERTEX
  421.         g_dev.DrawPrimitive D3DPT_TRIANGLESTRIP, 0, 2
  422.         i = m_Trees(i).iNext
  423.     Loop
  424.     'Next
  425.     ' Restore state
  426.     Dim matWorld As D3DMATRIX
  427.     D3DXMatrixIdentity matWorld
  428.     g_dev.SetTransform D3DTS_WORLD, matWorld
  429.     g_dev.SetRenderState D3DRS_ALPHATESTENABLE, 0 '   FALSE
  430.     g_dev.SetRenderState D3DRS_ALPHABLENDENABLE, 0 '  FALSE
  431. End Sub
  432. '-----------------------------------------------------------------------------
  433. ' Name: Render()
  434. ' Desc: Called once per frame, the call is the entry point for 3d
  435. '       rendering. This function sets up render states, clears the
  436. '       viewport, and renders the scene.
  437. '-----------------------------------------------------------------------------
  438. Function Render() As Boolean
  439.     Dim matView As D3DMATRIX, matViewSave As D3DMATRIX, hr As Long
  440.     Render = False
  441.     'See what state the device is in.
  442.     hr = g_dev.TestCooperativeLevel
  443.     If hr = D3DERR_DEVICENOTRESET Then
  444.         On Error Resume Next
  445.         g_dev.Reset g_d3dpp
  446.         If (Err.Number = D3D_OK) Then
  447.             RestoreDeviceObjects
  448.         End If
  449.         On Error GoTo 0
  450.     ElseIf hr <> 0 Then
  451.         Exit Function 'dont bother rendering if we are not ready yet
  452.     End If
  453.     Render = True
  454.     ' Clear the viewport
  455.     g_dev.Clear ByVal 0, ByVal 0, D3DCLEAR_ZBUFFER, &H0, 1, 0
  456.     ' Begin the scene
  457.     g_dev.BeginScene
  458.     ' Render the Skybox
  459.     ' Center view matrix for skybox and disable zbuffer
  460.         
  461.     g_dev.GetTransform D3DTS_VIEW, matViewSave
  462.     matView = matViewSave
  463.     matView.m41 = 0: matView.m42 = -0.3: matView.m43 = 0
  464.     g_dev.SetTransform D3DTS_VIEW, matView
  465.     g_dev.SetRenderState D3DRS_ZENABLE, 0 ' FALSE
  466.     ' Render the skybox
  467.     m_SkyBox.Render g_dev
  468.     ' Restore the render states
  469.     g_dev.SetTransform D3DTS_VIEW, matViewSave
  470.     g_dev.SetRenderState D3DRS_ZENABLE, 1 'TRUE
  471.     ' Draw the terrain
  472.     m_Terrain.Render g_dev
  473.     ' Draw the trees
  474.     DrawTrees
  475.         ' End the scene.
  476.     g_dev.EndScene
  477. End Function
  478. '-----------------------------------------------------------------------------
  479. ' Name: InitDeviceObjects()
  480. ' Desc: This creates all device-dependant managed objects, such as managed
  481. '       textures and managed vertex buffers.
  482. '-----------------------------------------------------------------------------
  483. Sub InitDeviceObjects()
  484.     Dim i As Long
  485.     Dim v As TREEVERTEX
  486.     ' Create the tree textures
  487.     For i = 0 To NUMTREETEXTURES - 1
  488.         Set m_TreeTextures(i) = g_d3dx.CreateTextureFromFileEx(g_dev, m_media + m_strTreeTextures(i), 256, 256, D3DX_DEFAULT, 0, D3DFMT_A1R5G5B5, D3DPOOL_MANAGED, D3DX_DEFAULT, D3DX_DEFAULT, &HFF000000, ByVal 0, ByVal 0)
  489.     Next
  490.     ' Create a quad for rendering each tree
  491.     Set m_TreeVB = g_dev.CreateVertexBuffer(4 * Len(v), 0, D3DFVF_TREEVERTEX, D3DPOOL_MANAGED)
  492.     ' Load the skybox
  493.     m_SkyBox.InitFromFile g_dev, m_media + "SkyBox2.x"
  494.     ' Load the terrain
  495.     m_Terrain.InitFromFile g_dev, m_media + "SeaFloor.x"
  496.     ' Add some "hilliness" to the terrain
  497.     Dim HillVB As Direct3DVertexBuffer8, NumHillVerts As Long
  498.     Dim HillVerts() As HILLVERTEX
  499.     Set HillVB = m_Terrain.mesh.GetVertexBuffer()
  500.     NumHillVerts = m_Terrain.mesh.GetNumVertices
  501.     ReDim HillVerts(NumHillVerts)
  502.     D3DVertexBuffer8GetData HillVB, 0, NumHillVerts * Len(HillVerts(0)), 0, HillVerts(0)
  503.     For i = 0 To NumHillVerts - 1
  504.         HillVerts(i).y = HeightField(HillVerts(i).x, HillVerts(i).z)
  505.     Next
  506.     D3DVertexBuffer8SetData HillVB, 0, NumHillVerts * Len(HillVerts(0)), 0, HillVerts(0)
  507. End Sub
  508. '-----------------------------------------------------------------------------
  509. ' Name: RestoreDeviceObjects()
  510. ' Desc: Restore device-memory objects and state after a device is created or
  511. '       resized.
  512. '-----------------------------------------------------------------------------
  513. Sub RestoreDeviceObjects()
  514.     ' Restore the device objects for the meshes and fonts
  515.     m_Terrain.RestoreDeviceObjects g_dev
  516.     m_SkyBox.RestoreDeviceObjects g_dev
  517.     ' Set the transform matrices (view and world are updated per frame)
  518.     Dim matProj As D3DMATRIX
  519.     D3DXMatrixPerspectiveFovLH matProj, g_pi / 4, Me.ScaleHeight / Me.ScaleWidth, 1, 100
  520.     g_dev.SetTransform D3DTS_PROJECTION, matProj
  521.     ' Set up the default texture states
  522.     g_dev.SetTextureStageState 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1
  523.     g_dev.SetTextureStageState 0, D3DTSS_COLORARG1, D3DTA_TEXTURE
  524.     g_dev.SetTextureStageState 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1
  525.     g_dev.SetTextureStageState 0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE
  526.     g_dev.SetTextureStageState 0, D3DTSS_MINFILTER, D3DTEXF_LINEAR
  527.     g_dev.SetTextureStageState 0, D3DTSS_MAGFILTER, D3DTEXF_LINEAR
  528.     g_dev.SetTextureStageState 0, D3DTSS_ADDRESSU, D3DTADDRESS_CLAMP
  529.     g_dev.SetTextureStageState 0, D3DTSS_ADDRESSV, D3DTADDRESS_CLAMP
  530.     g_dev.SetRenderState D3DRS_DITHERENABLE, 1 'TRUE
  531.     g_dev.SetRenderState D3DRS_ZENABLE, 1      'TRUE )
  532.     g_dev.SetRenderState D3DRS_LIGHTING, 0     'FALSE )
  533. End Sub
  534. '-----------------------------------------------------------------------------
  535. ' Name: InvalidateDeviceObjects()
  536. ' Desc: Called when the device-dependant objects are about to be lost.
  537. '-----------------------------------------------------------------------------
  538. Sub InvalidateDeviceObjects()
  539.     m_Terrain.InvalidateDeviceObjects
  540.     m_SkyBox.InvalidateDeviceObjects
  541. End Sub
  542. '-----------------------------------------------------------------------------
  543. ' Name: DeleteDeviceObjects()
  544. ' Desc: Called when the app is exitting, or the device is being changed,
  545. '       this function deletes any device dependant objects.
  546. '-----------------------------------------------------------------------------
  547. Sub DeleteDeviceObjects()
  548.     Dim i As Long
  549.     m_Terrain.Destroy
  550.     m_SkyBox.Destroy
  551.     For i = 0 To NUMTREETEXTURES - 1
  552.         Set m_TreeTextures(i) = Nothing
  553.     Next
  554.     m_bInit = False
  555. End Sub
  556. '-----------------------------------------------------------------------------
  557. ' Name: FinalCleanup()
  558. ' Desc: Called before the app exits, this function gives the app the chance
  559. '       to cleanup after itself.
  560. '-----------------------------------------------------------------------------
  561. Sub FinalCleanup()
  562.     Set m_Terrain = Nothing
  563.     Set m_SkyBox = Nothing
  564. End Sub
  565. '-----------------------------------------------------------------------------
  566. ' Name: VerifyDevice()
  567. ' Desc: Called during device intialization, this code checks the device
  568. '       for some minimum set of capabilities
  569. '-----------------------------------------------------------------------------
  570. Public Function VerifyDevice(usageflags As Long, format As CONST_D3DFORMAT) As Boolean
  571.     ' This sample uses alpha textures and/or straight alpha. Make sure the
  572.     ' device supports them
  573.     If ((g_d3dCaps.TextureCaps And D3DPTEXTURECAPS_ALPHAPALETTE) = D3DPTEXTURECAPS_ALPHAPALETTE) Then VerifyDevice = True
  574.     If ((g_d3dCaps.TextureCaps And D3DPTEXTURECAPS_ALPHA) = D3DPTEXTURECAPS_ALPHA) Then VerifyDevice = True
  575. End Function
  576.